Using Go's Variable Types
Get introduced to Go's variable types and learn how to declare them.
We'll cover the following
Modern programming languages are built with primitives called types. When we hear that a variable is a string or integer, we are talking about the variable’s type. With today’s programming languages, there are two common type systems used:
-
Dynamic types (also called duck typing)
-
Static types
Go is a statically typed language. For those who might be coming from languages such as Python, Perl, and PHP, then those languages are dynamically typed. In a dynamically typed language, we can create a variable and store anything in it. In those languages, the type simply indicates what is stored in the variable. Here is an example in Python:
In this case, v can store anything, and the type held by v is unknown without using some runtime checks (runtime meaning that it can't be checked at compile time). In a statically typed language, the type of the variable is set when it is created. That type cannot change. In this type of language, the type is both what is stored in the variable and what can be stored in the variable. Here is a Go example:
The v value cannot be set to any other type than a string. It might seem like Python is superior because it can store anything in its variable. But in practice, this lack of being specific means that Python must wait until a program is running before it can find out there is a problem (what we call a runtime error). It is better to find the problem when the software is compiled than when it is deployed. Let's take a look at a function to add two numbers together as an example. Here is the Python version:
Here is the Go version:
In the Python version, we can see that a and b will be added together. But what types are a and b? What is the result type? What happens if we pass an integer and a float or an integer and a string? In some cases, two types cannot be added together in Python, which will cause a runtime exception, and we can never be sure of what the result type will be.
Note: Python has added type hints to the language to help avoid these problems. But, practical experience has taught us with JavaScript, Dart, TypeScript, and Closure that while it can help, optional type support means that a lot of problems fall through the cracks.
Our Go version defines the exact types of our arguments and our result. We cannot pass an integer and a float or an integer and a string. We'll only ever receive an integer as a return. This allows our compiler to find any errors with variable types when the program is compiled. In Python, this error could show up at any time, from the instant it ran to 6 months later when a certain code path was executed.
Note: A few years ago, there was a study done on the Rosetta Code repository for some of the top languages in use to see how they fared in processing time, memory use, and runtime failures. For runtime failures, Go had the least failures, with Python towards the bottom of the ranking. Static typing would have certainly played into that.
Go's types#
Go has a rich type system that not only specifies that a type might be an integer but also the size of the integer. This allows a Go programmer to reduce the size of a variable both in memory and when encoding for network transport. The following table shows the most common types used in Go:
Common Go types
Type | Description |
| A 64-bit signed integer on 64-bit systems, 32 on 32-bit systems |
| A Boolean, either true or false |
| A string of UTF-8 characters |
| A 64-bit floating-point number |
| A growable list of items |
| Key-value pairs, similar to Python's dictionaries |
| A collection of named attributes (variables), similar to Python objects |
| A type that holds a value with specifically defined methods |
| A type that stores the memory address of a variable, not the variable |
| A buffered or non-buffered pipe for sending data asynchronously |
We’ll be keeping our discussion mostly to the preceding types; here is the full list
Go doesn't just provide these types; we can also create new types based on these basic types. These custom types become their own type and can have methods attached to them. Declaring a custom type is done with the type keyword and will be discussed during the lesson on the struct type. For now, we are going to move on to the basics of declaring variables. Now that we've talked about our variable types, let's have a look at how we can create them.
Declaring variables#
As in most languages, declaring a variable allocates storage that will hold some type of data. In Go, that data is typed so that only that type can be stored in the allocated storage. As Go has multiple ways to declare a variable, the next parts will talk about the different ways this can be done.
The long way to declare a variable#
The most specific way to declare a variable is using the var keyword. We can use var to declare a variable both at the package level (meaning not inside a function) and within a function. Let's look at some examples of ways to declare variables using var:
This declares an i variable that can hold an int64 type. No value is assigned, so the value is assigned the zero value of an integer, which is 0:
This declares an i variable that can hold an int type. The value 3 is assigned to i. Note that the int and int64 types are distinct. We cannot use an int type as an int64 type, and vice versa. However, we can do type conversions to allow interchanging these types:
Using (), we group together a set of declarations. i can hold an int type and has the integer zero value, 0. word doesn't declare the type, but it is inferred by the string value on the right side of the equal (=) operator.
The shorter way#
In the previous example, we used the var keyword to create a variable and the = operator to assign values. If we do not have an = operator, the compiler assigns the zero value for the type (more on this later). The important concept is as follows:
varcreated the variable but did not make an assignment.The equal (
=) operator assigned a value to the variable.
Within a function (not at the package level), we can do a create and assign by using the := operator. This both creates a new variable and assigns a value to it:
The important thing to remember when using := is that it means to create and assign. If the variable already exists, we cannot use :=, but must use =, which just does an assignment.
Utilizing Go Packages
Variable Scopes and Shadowing